package api

import (
	"encoding/json"
	"net/http"

	"docker-monitor/internal/docker"

	"github.com/gorilla/mux"
)

// NewRouter creates a new HTTP router with all API endpoints
func NewRouter(dockerService *docker.DockerService) *mux.Router {
	router := mux.NewRouter()

	// API routes
	api := router.PathPrefix("/api/v1").Subrouter()
	api.HandleFunc("/containers", listContainersHandler(dockerService)).Methods("GET")
	api.HandleFunc("/containers/{id}", getContainerHandler(dockerService)).Methods("GET")
	api.HandleFunc("/containers/{id}/stop", stopContainerHandler(dockerService)).Methods("POST")
	api.HandleFunc("/containers/{id}/restart", restartContainerHandler(dockerService)).Methods("POST")
	api.HandleFunc("/containers/{id}/start", startContainerHandler(dockerService)).Methods("POST")
	api.HandleFunc("/containers/{id}/remove", removeContainerHandler(dockerService)).Methods("DELETE")
	api.HandleFunc("/containers/{id}/logs", getContainerLogsHandler(dockerService)).Methods("GET")

	return router
}

// listContainersHandler returns a list of all containers
func listContainersHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		containers, err := dockerService.ListContainers()
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.Header().Set("Content-Type", "application/json")
		json.NewEncoder(w).Encode(containers)
	}
}

// getContainerHandler returns information about a specific container
func getContainerHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		vars := mux.Vars(r)
		containerID := vars["id"]

		container, err := dockerService.GetContainerInfo(containerID)
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.Header().Set("Content-Type", "application/json")
		json.NewEncoder(w).Encode(container)
	}
}

// stopContainerHandler stops a container
func stopContainerHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		vars := mux.Vars(r)
		containerID := vars["id"]

		err := dockerService.StopContainer(containerID)
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.WriteHeader(http.StatusOK)
		json.NewEncoder(w).Encode(map[string]string{"status": "success", "message": "Container stopped"})
	}
}

// restartContainerHandler restarts a container
func restartContainerHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		vars := mux.Vars(r)
		containerID := vars["id"]

		err := dockerService.RestartContainer(containerID)
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.WriteHeader(http.StatusOK)
		json.NewEncoder(w).Encode(map[string]string{"status": "success", "message": "Container restarted"})
	}
}

// startContainerHandler starts a container
func startContainerHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		vars := mux.Vars(r)
		containerID := vars["id"]

		err := dockerService.StartContainer(containerID)
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.WriteHeader(http.StatusOK)
		json.NewEncoder(w).Encode(map[string]string{"status": "success", "message": "Container started"})
	}
}

// removeContainerHandler removes a container
func removeContainerHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		vars := mux.Vars(r)
		containerID := vars["id"]

		err := dockerService.RemoveContainer(containerID)
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.WriteHeader(http.StatusOK)
		json.NewEncoder(w).Encode(map[string]string{"status": "success", "message": "Container removed"})
	}
}

// getContainerLogsHandler returns the logs of a container
func getContainerLogsHandler(dockerService *docker.DockerService) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		vars := mux.Vars(r)
		containerID := vars["id"]

		logs, err := dockerService.GetContainerLogs(containerID)
		if err != nil {
			http.Error(w, err.Error(), http.StatusInternalServerError)
			return
		}

		w.Header().Set("Content-Type", "text/plain")
		w.Write([]byte(logs))
	}
}